import json
import os
import constants
import testPo


class Interface:
    """
    负责调用C++接口的类
    """

    @staticmethod
    def under_sample(size, target, source):
        """
        根据给定的STL文件，以及size大小，进行降采样，减少点的数量

        :param size: 不是数量，越小点越多
        :param target: 目标点云
        :param source: 初始点云
        :return: 对应的两个txt文件名
        """
        print(1)
        command = f"{constants.commandBasePath}/under_sample {size} {target} {source}"
        result = os.popen(command).read()
        print(result)
        if not result.startswith("{\"success\""):
            return None

        resultDict = json.loads(result,strict=False)
        if resultDict["success"]:
            return list(resultDict["filenames"])[0], list(resultDict["filenames"])[1]
        else:
            return None

    @staticmethod
    def abs_rotation(target, source):
        """
        根据用户标点，获得大致的变换矩阵

        :param target: 目标点云
        :param source: 初始点云
        :return: 4*4变换矩阵
        """
        print(2)
        command = f"{constants.commandBasePath}/abs_rotation {target} {source}"
        result = os.popen(command).read()
        print(123,"fba",result)
        # if not result.startswith("{\"success\""):
            # return None
        resultDict = json.loads(result)
        # if resultDict["success"]:
        return list(resultDict["matrix"])
        # else:
        #     return None

    @staticmethod
    def add_align(target, source, iterations, matrix):
        """
        对上颌进行配准

        :param target: 目标点云
        :param source: 初始点云
        :param iterations: 迭代次数
        :param matrix: 4*4初始矩阵
        :return: 4*4变换矩阵
        """
        print(3)
        matrix = matrixToStr(matrix)
        command = f"{constants.commandBasePath}/add_align {target} {source} {iterations} {matrix}"
        result = os.popen(command).read()
        print(result)
        if not result.startswith("{\"success\""):
            return None

        resultDict = json.loads(result)
        if resultDict["success"]:
            return list(resultDict["matrix"])
        else:
            return None

    @staticmethod
    def key_points(target, source, iterations, matrix):
        """
        对下颌进行操作，求解出对应点

        :param target: 目标点云
        :param source: 初始点云
        :param iterations: 迭代次数
        :param matrix: 4*4矩阵（add_align所得）
        :return: 两个对应点的文件名，4*4变换矩阵
        """
        print(4)
        matrix = matrixToStr(matrix)
        command = f"{constants.commandBasePath}/key_points {target} {source} {iterations} {matrix}"
        result = os.popen(command).read()
        if not result.startswith("{\"success\""):
            return None
        print(result)
        resultDict = json.loads(result)
        if resultDict["success"]:
            return list(resultDict["filenames"]), list(resultDict["matrix"])
        else:
            return None

    @staticmethod
    def compute_axis(target, source, matrix):
        """
        根据下颌求得的对应点，求解旋转轴

        :param target: 目标点云
        :param source: 初始点云
        :param matrix: 变换矩阵
        :return: 一个含k1,b1,k2,b2的列表
        """
        print(5)
        matrix=[matrix[i*4:i*4+4] for i in range(4)]
        result = testPo.compute_axis(target, source, matrix)
        print(result)
        return result
        # reference=matrixToStr(reference)
        # matrix = matrixToStr(matrix)
        # command = f"{constants.commandBasePath}/compute_axis {target} {source} {reference} {matrix}"
        # result = os.popen(command).read()
        # print(result)
        # if not result.startswith("{\"success\""):
        #     return None

        # resultDict = json.loads(result)
        # if resultDict["success"]:
        #     res = list(resultDict["axis"])
        #     return res[0], res[1], res[2], res[3]
        # else:
        #     return None

def matrixToStr(matrix):
    newMatrix = [str(i) for i in matrix]
    newMatrix = " ".join(newMatrix)
    return newMatrix
